package com.bright.hxj.cwduijie.service.impl;

import com.bright.hxj.cwduijie.converter.AccCodeConverter;
import com.bright.hxj.cwduijie.enums.DataApi;
import com.bright.hxj.cwduijie.pojo.bo.ApiDataCollection;
import com.bright.hxj.cwduijie.pojo.dto.AccCodeDto;
import com.bright.hxj.cwduijie.pojo.dto.CheckResultDto;
import com.bright.hxj.cwduijie.pojo.po.AccCode;
import com.bright.hxj.cwduijie.pojo.query.DuijieQuery;
import com.bright.hxj.cwduijie.pojo.vo.AccCodeDataVO;
import com.bright.hxj.cwduijie.pojo.vo.AccCodeVO;
import com.bright.hxj.cwduijie.repository.AccCodeRepository;
import com.bright.hxj.cwduijie.service.AbstractPerThousandApiService;
import com.bright.hxj.cwduijie.util.EntityManagerUtil;
import com.bright.ghj.common.util.ListUtil;
import com.fasterxml.jackson.core.JsonProcessingException;
import lombok.RequiredArgsConstructor;
import lombok.extern.slf4j.Slf4j;
import org.springframework.data.jpa.repository.JpaSpecificationExecutor;
import org.springframework.stereotype.Component;

import java.util.*;
import java.util.function.Function;

/**
 * @Author hxj
 * @Date 2024/7/29 14:40
 * @Description
 */

@Component
@RequiredArgsConstructor
@Slf4j
public class ApiAccCodeServiceImpl extends AbstractPerThousandApiService<AccCodeDto> {

    private final AccCodeRepository accCodeRepository;
    private final AccCodeConverter accCodeConverter;

    @Override
    public JpaSpecificationExecutor getJpaSpecificationExecutor() {
        return accCodeRepository;
    }

    @Override
    public DataApi getDataApi() {
        return DataApi.ACC_CODE;
    }

    @Override
    public Function<AccCodeDto, Integer> getIdFunc() {
        return AccCodeDto::getId;
    }

//    @Override
//    public List<String> getNeedDuijieZtDataKeys() {
//        List<String> dataKeys = accCodeRepository.getDistinctZtDataKeyBySjjhbz(SJJHBZ.WAITING.getValue());
//        dataKeys.addAll(accCodeRepository.getDistinctZtDataKeyBySjjhbz(SJJHBZ.ERROR.getValue()));
//        return dataKeys;
//    }

    @Override
    public boolean isExistsTYSHXYDMField() {
        return false;
    }

    @Override
    protected void getData(ApiDataCollection apiDataCollection, DuijieQuery duijieQuery) {
        // 科目需要有年份条件 如果没传年份 就取当年
        Integer years = duijieQuery.getDuijieYears() == null ? Calendar.getInstance().get(Calendar.YEAR) : duijieQuery.getDuijieYears();
//        List<AccCode> accCodes = accCodeRepository.getAccCodesByZTDATAKEYAndYearsAndSjjhbz(duijieQuery.getZtDataKey(), SJJHBZ.WAITING.getValue(), OpType.ADD_OR_EDIT.getValue(), years);
//        accCodes.addAll(accCodeRepository.getAccCodesByZTDATAKEYAndYearsAndSjjhbz(duijieQuery.getZtDataKey(), SJJHBZ.ERROR.getValue(), OpType.ADD_OR_EDIT.getValue(), years));
//        List<AccCode> accCodes = accCodeRepository.getAccCodesByZTDATAKEYAndYears(duijieQuery.getZtDataKey(), OpType.ADD_OR_EDIT.getValue(), years);
//        // 筛查一下是否有0跟2的数据 如果有就全部重推（因为本接口是按账套全量覆盖型接口）
//        long count = ListUtil.countByFilter(accCodes, accCode -> accCode.getSjjhbz() == SJJHBZ.WAITING.getValue() || accCode.getSjjhbz() == SJJHBZ.ERROR.getValue());
//        apiDataCollection.setAccCodes(count > 0 ? accCodeConverter.poConvertDTO(accCodes) : Collections.emptyList());

        String queryCountSQL = "select count(*) from DJ_KMCSHSJ with(nolock) where opType=1 and sjjhbz in (0,2) and NF=:years and ZT_DATA_KEY=:ztDataKey";
        Map<String, Object> params = new HashMap<>();
        params.put("years", years);
        params.put("ztDataKey", duijieQuery.getZtDataKey());
        Long count = EntityManagerUtil.queryForCount(entityManager, queryCountSQL, params);
        List<AccCode> accCodes;
        if (count > 0) {
            String querySQL = "SELECT id as id, ZT_DATA_KEY, SJKM_BM, BM, MC, YEFX, CJ, SFYXKSXJKM, SLHS_QYZT, SLHS_DW, FZHS_QYZT, convert(varchar(50),QCYE_JE) QCYE_JE, convert(varchar(50),QCYE_SL) QCYE_SL, convert(varchar(50),BNLJ_JE_JF) BNLJ_JE_JF, convert(varchar(50),BNLJ_SL_JF) BNLJ_SL_JF, convert(varchar(50),BNLJ_JE_DF) BNLJ_JE_DF, convert(varchar(50),BNLJ_SL_DF) BNLJ_SL_DF, sjjhbz as sjjhbz, opType as opType, taskId as taskId, djflag as djflag " +
                    "from DJ_KMCSHSJ with(nolock) where opType=1 and NF=:years and ZT_DATA_KEY=:ztDataKey";
            accCodes = EntityManagerUtil.queryForClass(entityManager, querySQL, params, AccCode.class);
        } else {
            // 科目数据不需要重推 传空列表跳过该接口
            accCodes = Collections.emptyList();
        }
        apiDataCollection.setAccCodes(accCodeConverter.poConvertDTO(accCodes));
    }

    @Override
    public Function<AccCodeDto, String> getDataKeyFunc() {
        return null;
    }

    @Override
    public Function<ApiDataCollection, List<AccCodeDto>> getDataFunc() {
        return ApiDataCollection::getAccCodes;
    }

    @Override
    protected void checkDataValid(Map<String, CheckResultDto> checkResultDtoMap, ApiDataCollection apiDataCollection) {
        checkService.checkDataBeforeSend(checkResultDtoMap, apiDataCollection.getAccCodes(), getDataApi(), getIdFunc());
    }

    @Override
    public void sendData(ApiDataCollection apiDataCollection, DuijieQuery duijieQuery, String batchId) throws JsonProcessingException {
        List<AccCodeDto> accCodeDtos = apiDataCollection.getAccCodes();
        AccCodeDataVO accCodeDataVO;
        if (accCodeDtos.size() == 0) {
            log.debug("无需要对接的科目初始化数据，该接口跳过，账套标识：" + duijieQuery.getZtDataKey());
            // 没数据就传空
            accCodeDataVO = null;
        } else {
            accCodeDataVO = new AccCodeDataVO();
            accCodeDataVO.setZT_DATA_KEY(duijieQuery.getZtDataKey());
            accCodeDataVO.setTYSHXYDM(duijieQuery.getCreditCode());

            List<AccCodeVO> accCodeVOS = accCodeConverter.dtoConvertVO(accCodeDtos);
            accCodeDataVO.setKJKM_LIST(accCodeVOS);
        }
        sendObjectData(accCodeDataVO, DataApi.ACC_CODE, ListUtil.toSingleList(accCodeDtos, AccCodeDto::getId), batchId, duijieQuery.getAccSet());
    }

//    @Override
//    protected List<AccCodeDto> getNeedDeleteData(DuijieQuery duijieQuery) {
//        return null;
//    }

    @Override
    public DataApi getDeleteDataApi() {
        return null;
    }

    @Override
    protected String getCheckDuplicateGroupByFields() {
        return "ZT_DATA_KEY, NF, BM";
    }
}
